﻿Imports System.Globalization

'******************************* File Header *********************************
'* File Name:    WmiConnectionStringBuilder.vb
'* Project:      WmiConnection
'* Copyright (c) Freddy Kuehne
'*
'* Default implementation for a wmi connection string builder.
'* 
'* This source is subject to the GNU Library General Public License (LGPL).
'* See http://wmiconnection.codeplex.com/license.
'* All other rights reserved.
'*****************************************************************************

''' <summary>
''' Provides a simple way to create and manage the contents of connection strings used by the WmiConnection class.
''' </summary>
Public Class WmiConnectionStringBuilder
  Inherits DbConnectionStringBuilder
#Region "Constructors"
  ''' <summary>
  ''' Creates a new connection string builder.
  ''' </summary>
  Public Sub New()
    MyBase.New()
    ResetProperties()
  End Sub

  ''' <summary>
  ''' Creates a new connection string builder.
  ''' </summary>
  ''' <param name="server"><see cref="Server"/></param>
  ''' <param name="path"><see cref="Path"/></param>
  ''' <param name="user"><see cref="UserID"/></param>
  ''' <param name="password"><see cref="Password"/></param>
  Public Sub New(ByVal server As String, ByVal path As String, ByVal user As String, ByVal password As String)
    Me.New()
    Me.Server = server
    Me.Path = path
    Me.UserID = user
    Me.Password = password
  End Sub

  ''' <summary>
  ''' Creates a new connection string builder.
  ''' </summary>
  ''' <param name="connectionString"><see cref="DbConnectionStringBuilder.ConnectionString"/></param>
  Public Sub New(ByVal connectionString As String)
    Me.New()
    Me.ConnectionString = connectionString
  End Sub
#End Region

#Region "Properties"
  ''' <summary>
  ''' Gets or sets the name or network address of the instance of WMI Server to connect to.
  ''' </summary>
  Public Property Server As String
    Get
      Server = CStr(Item("server"))
    End Get
    Set(ByVal value As String)
      Item("server") = value
    End Set
  End Property

  ''' <summary>
  ''' <see cref="Path"/>
  ''' </summary>
  Public Property Database As String
    Get
      Database = Path
    End Get
    Set(ByVal value As String)
      Path = value
    End Set
  End Property

  ''' <summary>
  ''' Gets or sets the root namespace to be used when connecting to the WMI Server. 
  ''' </summary>
  Public Property Path As String
    Get
      Path = CStr(Item("path"))
    End Get
    Set(ByVal value As String)
      Item("path") = value
      Item("database") = value
    End Set
  End Property

  ''' <summary>
  ''' Gets or sets the user ID to be used when connecting to the WMI Server. 
  ''' </summary>
  Public Property UserID As String
    Get
      UserID = CStr(Item("userid"))
    End Get
    Set(ByVal value As String)
      Item("userid") = value
    End Set
  End Property

  ''' <summary>
  ''' Gets or sets the password to be used when connecting to the WMI Server. 
  ''' </summary>
  Public Property Password As String
    Get
      Password = CStr(Item("password"))
    End Get
    Set(ByVal value As String)
      Item("password") = value
    End Set
  End Property

  ''' <summary>
  ''' Gets or sets an item to be used when connecting to the WMI Server. 
  ''' </summary>
  Default Public Overrides Property Item(keyword As String) As Object
    Get
      Item = Nothing
      TryGetValue(TransformItemKey(keyword), Item)
    End Get
    Set(value As Object)
      MyBase.Item(TransformItemKey(keyword)) = value
    End Set
  End Property

  ''' <summary>
  ''' Builds the WMI scope.
  ''' </summary>
  Friend ReadOnly Property Scope As String
    Get
      Scope = Path
      If (String.IsNullOrEmpty(Scope)) Then Scope = "\root\cimv2"
      If (Not Scope.StartsWith("\", StringComparison.OrdinalIgnoreCase)) Then Scope = "\" + Scope
      If (Not String.IsNullOrEmpty(Server)) Then Scope = "\\" + Server + Scope
    End Get
  End Property

  ''' <summary>
  ''' Builds an connectionoptions instance.
  ''' </summary>
  Friend ReadOnly Property Options As ConnectionOptions
    Get
      Options = Nothing
      If (Not String.IsNullOrEmpty(UserID)) Then
        Options = New ConnectionOptions
        Options.Username = UserID
        Options.Password = Password
      End If
    End Get
  End Property
#End Region

#Region "Methods"
  ''' <summary>
  ''' Transform the key name to a normalized form.
  ''' </summary>
  ''' <param name="key">key name</param>
  ''' <returns>transformed key name</returns>
  ''' <exception cref="ArgumentNullException">Exception occurs, when an empty <paramref name="key"/> is passed</exception>
  Private Shared Function TransformItemKey(key As String) As String
    If (key Is Nothing) Then Throw New ArgumentNullException("key")
    key = key.ToLowerInvariant
    If (String.Equals("database", key, StringComparison.Ordinal)) Then key = "path"
    TransformItemKey = key
  End Function

  ''' <summary>
  ''' Resets the connections properties.
  ''' </summary>
  Private Sub ResetProperties()
    Server = String.Empty
    Path = String.Empty
    UserID = String.Empty
    Password = String.Empty
  End Sub
#End Region
End Class
